package com.csproj.system.service;


import com.csproj.siiat.base.common.dto.BaseDTO;
import com.csproj.siiat.base.common.exception.BaseAppException;
import com.csproj.system.domain.AuthorityInfo;
import com.csproj.system.domain.RoleInfo;
import com.csproj.system.domain.UserInfo;
import com.csproj.system.repository.AuthorityInfoRepository;
import com.csproj.system.repository.RoleInfoRepository;
import com.csproj.system.repository.UserInfoRepository;
import com.csproj.system.service.dto.RoleInfoDTO;
import com.csproj.system.service.mapper.AuthorityInfoMapper;
import com.csproj.system.service.mapper.RoleInfoMapper;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;
import java.util.stream.Collectors;

/**
 * Service Implementation for managing RoleInfo.
 */
@Service
@Transactional
public class RoleInfoService {

    private final Logger log = LoggerFactory.getLogger(RoleInfoService.class);

    private final RoleInfoRepository roleInfoRepository;

    private final RoleInfoMapper roleInfoMapper;

    private final AuthorityInfoRepository authorityInfoRepository;

    private final AuthorityInfoMapper authorityInfoMapper;

    private final UserInfoRepository userInfoRepository;

    public RoleInfoService(RoleInfoRepository roleInfoRepository, RoleInfoMapper roleInfoMapper, AuthorityInfoRepository authorityInfoRepository, AuthorityInfoMapper authorityInfoMapper, UserInfoRepository userInfoRepository) {
        this.roleInfoRepository = roleInfoRepository;
        this.roleInfoMapper = roleInfoMapper;
        this.authorityInfoRepository = authorityInfoRepository;
        this.authorityInfoMapper = authorityInfoMapper;
        this.userInfoRepository = userInfoRepository;
    }

    /**
     * 保存角色信息
     * @param roleInfoDTO 角色DTO
     * @return BaseDTO
     */
    public BaseDTO save(RoleInfoDTO roleInfoDTO) {

        RoleInfo roleInfoname = roleInfoRepository.findByName(roleInfoDTO.getName());

        if(StringUtils.isNotBlank(roleInfoDTO.getId())){
            if(roleInfoname!=null && !roleInfoname.getId().equals(roleInfoDTO.getId())) {
                throw new BaseAppException(false,"duplicate_name");
            }

        }else if(roleInfoname!=null){
            throw  new BaseAppException(false,"duplicate_name");
        }
        log.debug("Request to save Role : {}", roleInfoDTO);
        RoleInfo roleInfo = roleInfoMapper.toEntity(roleInfoDTO);
        roleInfo.setDeletedFlag(false);

        if(roleInfoDTO.getId()!=null){
            RoleInfo r= roleInfoRepository.findOne(roleInfoDTO.getId());
            if(r!=null){
                roleInfo.setAuthorityInfos(r.getAuthorityInfos());
            }
        }
        roleInfo = roleInfoRepository.save(roleInfo);
        RoleInfoDTO result = roleInfoMapper.toDto(roleInfo);
        return BaseDTO.createBaseDTO(result);
    }

    /**
     *  获取所有角色信息
     *  @return the list of entities
     */
    @Transactional(readOnly = true)
    public List<RoleInfoDTO> findAll() {
        log.debug("Request to get all Roles");
        List<RoleInfoDTO> result = roleInfoRepository.findAllWithEagerRelationships().stream()
            .map(roleInfoMapper::toDto)
            .collect(Collectors.toCollection(LinkedList::new));
        return result;
    }

    /**
     * 获取角色信息（分页）
     * @param hsql          sql语句
     * @param queryParams   参数
     * @param pageable      分页对象
     * @return BaseDTO
     */
    @Transactional(readOnly=true)
    public BaseDTO findPageList(String hsql,Map<String, Object> queryParams,Pageable pageable) {
        Page<RoleInfo> result = roleInfoRepository.findPageList(hsql, queryParams, pageable);
        List<RoleInfoDTO> roleInfoDTOs = result.getContent().stream().
            map(r -> roleInfoMapper.toDto(r)
                   /* .setAuthorityInfos(r.getAuthorityInfos().stream().map(
                        a -> authorityInfoMapper.authorityInfoToAuthorityInfoDTO(a)
                    ).collect(Collectors.toSet()))*/
            ).collect(Collectors.toList());
        return BaseDTO.createBaseDTO(result).setFieldList(roleInfoDTOs);
    }

    /**
     *  获取角色对象
     *  @param 	id		角色id
     *  @return RoleInfoDTO	角色DTO
     */
    @Transactional(readOnly = true)
    public RoleInfoDTO findOne(String id) {
        log.debug("Request to get Role : {}", id);
        RoleInfo r1 = roleInfoRepository.findOneAuthNotNull(id);
        RoleInfo r2 = roleInfoRepository.findOne(id);
        RoleInfo result = null;
        if(r1 == null && r2 != null) {
            r2.setAuthorityInfos(null);
            result = r2;
        }
        if(r1 != null) {
            result = r1;
        }
        RoleInfoDTO roleInfoDTO = roleInfoMapper.toDto(result);
        return roleInfoDTO;
    }

    /**
     *  Delete the  role by id.
     *
     *  @param id the id of the entity
     */
    public void delete(String id) {
        log.debug("Request to delete Role : {}", id);
        RoleInfo roleInfo = roleInfoRepository.findOne(id);
        List<UserInfo> userInfos = userInfoRepository.getUserInfoByRoleInfoId(id);
        for (UserInfo userInfo : userInfos) {
            userInfo.getRoleInfos().remove(roleInfo);
            userInfoRepository.save(userInfo);
        }
        roleInfoRepository.delete(id);
        //添加操作记录

        //保存用户操作
    }

    /**
     * 获取所有角色  不分页
     * @return
     */
    public BaseDTO getRoleNonsort(){
        List<RoleInfoDTO> roleInfoDTOs = roleInfoRepository.findAll().stream().map(
            r -> roleInfoMapper.toDto(r)
        ).collect(Collectors.toList());
        return BaseDTO.createBaseDTO().setData(roleInfoDTOs);
    }

    /**
     *
     * @param id
     * @param ids
     */
    public void authorizeById(String id, List<String> ids) {
        RoleInfo roleInfo = roleInfoRepository.findOne(id);
        Set<AuthorityInfo> authorityInfos = new HashSet<>();
        ids.forEach(authorityInfoId->{
            AuthorityInfo authorityInfo = new AuthorityInfo();
            authorityInfo.setId(authorityInfoId);
            authorityInfos.add(authorityInfo);
        });
        roleInfo.setAuthorityInfos(authorityInfos);
    }

    /**
     * 设置角色的使用状态：禁用，启用，默认为启用
     * @param roleInfoDTO
     * @return
     */
    public RoleInfoDTO updateRoleInfoStatus(RoleInfoDTO roleInfoDTO){
        log.debug("Request to update UserInfo isUse : {}", roleInfoDTO);
        RoleInfo roleInfo = roleInfoRepository.findOne(roleInfoDTO.getId());
        Boolean isUse = roleInfo.getUsedFlag();
        if (isUse != null && !"".equals(isUse)) {
            roleInfo.setUsedFlag(isUse);
        }else {
            roleInfo.setUsedFlag(true);
        }
        roleInfo.setRemark(roleInfoDTO.getRemark());
        roleInfo = roleInfoRepository.save(roleInfo);
        RoleInfoDTO result = roleInfoMapper.toDto(roleInfo);
        return result;
    }
}
